﻿//*** Guidance generated code ***//
using System;
using System.Collections.Generic;
using System.Linq;

using Microsoft.VisualStudio.TestTools.UnitTesting;

using ProjectBase.Core;
using ProjectBase.Mvc;

using $prjsn$.Common;
using $prjsn$.Common.Business.Services;
using $prjsn$.Entity.Services;

namespace $safeprojectname$.CodeLists
{
    /// <summary>
    /// Some test for ContentType
    /// </summary>
    [TestClass]
    public class ContentTypeTest : EntityTestBase<IContentTypeFacade>
    {
        #region Test service stuff
        /// <summary>
        /// RE-use. Let's this method converts any entity into valid one
        /// (for all tests do it ones - here)
        /// </summary>
        /// <param name="entity"></param>
        /// <returns></returns>
        protected virtual ContentType MakeItValid(ContentType entity)
        {
            Messages.Clear();
            entity = entity ?? Facade.CreateNew(); // FACTORY METHOD design pattern
            entity.Code = Guid.NewGuid().ToString().ToLength(10);
            entity.Suffix = entity.Code;
            entity.Description = entity.Code;
            entity.IsVisible = true;

            return entity;
        }
        #endregion Test service stuff

        #region Get
        [TestMethod]
        public void FindDefaultCode()
        {
            var filter = new ContentTypeFilter
            {
                Code = "text/xml",
                TakeRows = 1,
            };
            var result = Facade.Find(filter);
            Assert.IsTrue(result.Count() > 0, " there must be ContentType entity which meets provided filtering criteria ");
            Assert.IsTrue(result.First().Code.Equals("text/xml"));
        }
        [TestMethod]
        public void GetByDefaultCode()
        {
            var result = Facade.GetByCode("text/xml");
            Assert.IsTrue(result.Is(), " there must be ContentType entity which meets provided filtering criteria ");
            Assert.IsTrue(result.Code.Equals("text/xml"));
        }
        #endregion Get

        #region Set
        /// <summary>
        /// Firstly tries to store 'business-point-of-view' incorrect entity - to get an Error Message.
        /// Secondly MakesItValid to assure the this will be stored
        /// </summary>
        [TestMethod]
        public void NewContentType()
        {
            Messages.Clear();
            //   I. Ask Facade to get new (pre-filled but not valid - e.g. Suffix is missing)
            var entity = Facade.CreateNew();

            //  II. Assure that Facade won't allow to store this
            entity = Facade.Add(entity);
            Assert.IsTrue(entity.IsTransient());
            Assert.IsTrue(Messages.ContainsError());


            // III. Make entity valid
            Messages.Clear();
            entity = MakeItValid(entity);

            //  IV. Assure that valid will be stored
            entity = Facade.Add(entity);

            Assert.IsFalse(Messages.ContainsError(), Messages.GetErrorMessage());
            Assert.IsFalse(entity.IsTransient(), " MakeItValid was called, so 'ContentType' Entity must be storable and NOT Transient now");
        }

        /// <summary>
        /// Tries to store similar entity (e.g. code property)
        /// to get the Error Message 'AlreadyExists'
        /// </summary>
        [TestMethod]
        public void AlreadyExistsContentTypeCheck()
        {
            //   I. Get existing entity from DB
            var oldEntity = Facade.Find(new ContentTypeFilter { TakeRows = 1 }).SingleOrDefault();
            if (oldEntity.IsNull())
            {
                Assert.Inconclusive(" To run this test there must be at least one 'ContentType' entity in DB ");
                return;
            }

            //  II. Create new transient 'VALID' entity
            var entity = MakeItValid(null);

            // III. Set the property to get similar entities, which should be prohibited
            entity.Code = oldEntity.Code;

            //  IV. Call Facade to store new one
            Messages.Clear();
            entity = Facade.Add(entity);

            //   V. Facade must stop storing this
            Assert.IsTrue(entity.IsTransient());
            Assert.IsTrue(Messages.ContainsError());
        }

        /// <summary>
        /// Test that UPDATE checks are working
        /// </summary>
        [TestMethod]
        public void UpdateContentType()
        {
            // I. get existing
            var entity = Facade.Find(new ContentTypeFilter { TakeRows = 1 }).SingleOrDefault();
            if (entity.IsNull())
            {
                Assert.Inconclusive(" there is no Entity record in DB Storage to test update");
                return;
            }

            // II. change it to get error
            Messages.Clear();
            entity.Code = null;

            // TODO change to get failures
            entity = Facade.Update(entity);

            // III. check there are errors
            Assert.IsTrue(Messages.ContainsError(), " There must be generated Error messages for not completely provided entity");

            Messages.Clear();
            // IV. repair it and check it will be stored

            entity = MakeItValid(entity);

            entity = Facade.Update(entity);
            // V. now it must be OK
            Assert.IsFalse(Messages.ContainsError(), Messages.GetErrorMessage());
        }

        /// <summary>
        /// Essential TEST !!!!!
        /// !!!!!!!!!!!!!!!!!!!!
        ///
        /// Assure there, that your entity cannot be delted, when is used by another entity!
        /// It will help you! soon, you'll see...
        /// </summary>
        //[TestMethod]
        public void DeleteContentType()
        {
            Messages.Clear();
        }
        #endregion Set

        #region Additional test attributes
        // constructor
        [ClassInitialize]
        public static void MyClassInitialize(TestContext testContext) { }

        [ClassCleanup]
        public static void MyClassCleanup() { }

        [TestInitialize]
        public override void MyTestInitialize() { base.MyTestInitialize(); }

        [TestCleanup]
        public override void MyTestCleanup() { base.MyTestCleanup(); }
        #endregion Additional test attributes
    }
}